--localize getter for intensity
local get_intensity = mob_spawning_director.get_intensity


local disabled


local loop_length = 6.0 - 0.1

-- State tracking stuff
local current_level = 0
local current_music = {}
local last_intensity = 0
local last_update_time = 0

local track_name_transit = "mood_music_transit"
local track_name_leveled = "mood_music_level"


local function adjust_intensity()
	local intensity = get_intensity()
	intensity = intensity + math.max(0, intensity - last_intensity) * 3

	last_intensity = intensity
	local intensity_levels = {0.05, 0.35, 0.6, 0.8, 1}
	
	
	for i, v in ipairs(intensity_levels)
	do
		if intensity <= v
		then
			if current_level > i - 1
			then
				current_level = current_level - 1
			elseif current_level < i - 1
			then
				current_level = current_level + 1
			end
			break
		end
	end
end

--plays to all players if player_name is nil
local function start_music(player_name)
	local gain
	local track_name
	
	if current_level > 0
	then
		gain = 0.2 + current_level * 0.15
		track_name = track_name_leveled .. current_level
	else
		track_name = track_name_leveled .. 1
		gain = 0.3
	end
	
	current_music[player_name or 1] = minetest.sound_play(track_name,
		{
			to_player = player_name,
			gain = gain,
			loop = true,
		})
end

local function stop_all_music()
	for name, song in pairs(current_music)
	do
		minetest.sound_stop(song)
		current_music[name] = nil
	end
end


local function update()
	
	local last_level = current_level
	
	adjust_intensity()
	
	if last_level ~= current_level
	then
		stop_all_music()
		
		--start new music
		start_music()
		
		--play transit track
		if last_level > 0
		then
			minetest.sound_play(track_name_transit, {
				gain = 0.2 + last_level * 0.1
			})
		end
	end
end




--control
------------------------------------------------------------------------
minetest.register_on_joinplayer(function(player)
		--start the music for the player
		--the music gets synchronized for all players once the
		--intensity changes
		local name = player:get_player_name()
		start_music(name)
	end)

minetest.register_globalstep(function(dtime)
	if disabled
	then
		return
	end
	local time = os.time()
	if current_level > 0
	then
		if time < last_update_time + loop_length
		then
			return
		end
	end
	last_update_time = time
	update()
end)



--api
------------------------------------------------------------------------
mood_music = {}


function mood_music.start()
	disabled = false
end

function mood_music.stop()
	disabled = true
	stop_all_music()
end
